<?php
declare (strict_types = 1);
namespace app\admin\controller;

use think\Request;
use think\Exception;
use think\exception\ValidateException;

use service\JsonService as Json;
use app\admin\controller\BaseController;

use app\common\model\User;
use app\common\model\OkrRecord;
use app\common\model\RuleKpi;
use app\common\model\RuleKpiBusin;
use app\common\model\KpiRecord;
use app\common\model\UserResume;
use app\common\model\ResumeRecord;
use app\common\model\Job;
use app\common\model\RuleOkr;
use app\common\model\KpiDaily;
use app\common\model\KpiDailyRule;

use app\common\validate\OkrValidate;
use LDAP\Result;

class AchievController extends BaseController
{
    /**
     * 获取OKR规则列表
     */
    public function getOkrRuleList()
    {
        $list  = RuleOkr::getList([], 0, 0, 0, '*', 'stage, id');
        $stage = [1 => '第一阶段', 2 => '第二阶段', 3 => '第三阶段', 4 => '第四阶段'];

        foreach($list as &$info){
            $info['stage_name'] = $stage[$info['stage']];
        }

        return Json::success('ok', $list);
    }

    /**
     * OKR规则编辑
     */
    public function setOkrRule()
    {
        $param['id']         = Request()->param('id', 0);
        $param['invite_num'] = Request()->param('invite_num', 0);
        $param['face_num']   = Request()->param('face_num', 0);
        $param['pass_num']   = Request()->param('pass_num', 0);

        $flag = RuleOkr::edit($param);
        if(!$flag) return Json::fail();
        return Json::success();
    }




    /** 获取OKR记录 */
    public function getOkrList()
    {   
        $page = Request()->param('page', 1);
        $isStaff = Request()->param('is_staff', 0);

        $where = [];

        if($isStaff == 1) $where[] = ['user_id', '=', $this->user_id];

        $list = OkrRecord::getList($where, 1, $page, 20, '*', 'create_time DESC, user_id, stage');
        if($list === false) return Json::fail('暂无数据');

        $grade = [0 => '', 1 => 'A', 2 => 'B', 3 => 'C', 4 => 'D', 5 => 'E'];

        foreach($list as &$info){
            $info['user_name']  = User::getVal(['id' => $info['user_id']], 'name');
            $info['admin_name'] = User::getVal(['id' => $info['admin_id']], 'name');
            $info['grade_okr']  = $grade[$info['grade_okr']];

            unset($info['user_id']);
            unset($info['admin_id']);
        }

        return Json::success('ok', $list, OkrRecord::getNum($where));
    }

    /**
     * 添加OKR数据(废弃)
     */
    public function addOkr()
    {
        $userId = Request()->param('user_id', 0);
        $param  = Request()->param('okr_data', '');
        if($userId == 0) return Json::fail('员工不能为空');
        if(empty($param)) return Json::fail('提交数据不能为空');

        $okrData = json_decode($param, true);

        foreach($okrData as $info){
            try{
                validate(OkrValidate::class)->scene('add')->check($info);
            }catch(ValidateException $e){
                return Json::fail($e->getError());
            }
        }

        $okrAddData = [];
        foreach($okrData as $info){
            $okrInfo = [
                'admin_id'    => $this->user_id,
                'user_id'     => $userId,
                'invite_num'  => $info['invite_num'],
                'face_num'    => $info['face_num'],
                'pass_num'    => $info['pass_num'],
                'stage'       => $info['stage'],
                'start_time'  => strtotime($info['start_time']),
                'end_time'    => strtotime($info['end_time']),
                'create_time' => time(),
            ];

            $okrAddData[] = $okrInfo;
        }

        $flag = OkrRecord::addAll($okrAddData);
        if(!$flag) return Json::fail('添加失败');
        return Json::success('添加成功');
    }

    /**
     * 生成OKR
     */
    public function setOkr()
    {
        OkrRecord::addOkr();
        return Json::success();
    }




    /**
     * 新增KPI规则
     */
    public function addKpi()
    {
        $paramJson = Request()->param('datas', '');
        if(empty($paramJson)) return Json::fail('参数错误');

        $param = json_decode($paramJson, true);

        foreach($param as &$info){
            if(!isset($info['total_low']) || empty($info['total_low'])) return Json::fail('业绩（低）不能为空');
            if(!isset($info['total_high']) || empty($info['total_high'])) return Json::fail('业绩（高）不能为空');
            if(!isset($info['radio']) || empty($info['radio'])) return Json::fail('提成比例不能为空');
            if(!isset($info['data_time']) || empty($info['data_time'])) return Json::fail('适用时间不能为空');

            if($this->user_id == 1) $info['status'] = 1;

            $info['data_time']   = strtotime($info['data_time']);
            $info['admin_id']    = $this->user_id;
            $info['create_time'] = time();
        }

        $flag = RuleKpi::addAll($param);
        if(!$flag) return Json::fail();
        return Json::success();
    }

    /**
     * KPI规则列表
     */
    public function getRuleKpiList()
    {
        $page  = Request()->param('page', 1);
        $isAll = Request()->param('is_all', 1);

        $where = [];

        if($this->user_id != 1){
            $where[] = ['status', '=', 1];
        }else{
            $where[] = ['status', 'in', [0, 1]];
        }

        if($isAll == 0) $where[] = ['data_time', '=', strtotime(date('Y-m', time()))];

        $list = RuleKpi::getList($where, 1, $page, 20, '*', 'status, data_time DESC, total_low');
        if(!$list) return Json::fail('暂无数据');
        return Json::success('ok', $list, RuleKpi::getNum($where));
    }

    /**
     * KPI规则编辑
     */
    public function setKpiRule()
    {
        $param['id']         = Request()->param('id', 0);
        $param['admin_id']   = $this->user_id;
        $param['total_low']  = Request()->param('total_low', 0);
        $param['total_high'] = Request()->param('total_high', 0);
        $param['radio']      = Request()->param('radio', 0);
        $param['data_time']  = strtotime(Request()->param('data_time', 0));

        $flag = RuleKpi::edit($param);
        if(!$flag) return Json::fail();
        return Json::success();
    }

    /**
     * KPI规则通过|驳回
     */
    public function setKpiRuleStatus()
    {
        $kpiRuleId = Request()->param('kpi_rule_id', 0);
        $status    = Request()->param('status', 0);
        if($status != 1 && $status != 2) return Json::fail('参数错误');

        $flag = RuleKpi::edit(['id' => $kpiRuleId, 'status' => $status]);
        if(!$flag) return Json::fail();
        return Json::success();
    }



    /**
     * 新增商务KPI规则
     */
    public function addKpiBusin()
    {
        $paramJson = Request()->param('datas', '');
        if(empty($paramJson)) return Json::fail('参数错误');

        $param = json_decode($paramJson, true);

        foreach($param as &$info){
            if(!isset($info['join_low']) || empty($info['join_low'])) return Json::fail('入职数量（低）不能为空');
            if(!isset($info['join_high']) || empty($info['join_high'])) return Json::fail('入职数量（高）不能为空');
            if(!isset($info['radio']) || empty($info['radio'])) return Json::fail('提成比例不能为空');
            if(!isset($info['data_time']) || empty($info['data_time'])) return Json::fail('适用时间不能为空');

            $info['data_time']   = strtotime($info['data_time']);
            $info['admin_id']    = $this->user_id;
            $info['create_time'] = time();
        }

        $flag = RuleKpiBusin::addAll($param);
        if(!$flag) return Json::fail();
        return Json::success();
    }

    /**
     * 商务KPI规则列表
     */
    public function getRuleKpiBusinList()
    {
        $page  = Request()->param('page', 1);
        $isAll = Request()->param('is_all', 1);

        $where = [];

        if($isAll == 0) $where[] = ['data_time', '=', strtotime(date('Y-m', time()))];

        $list = RuleKpiBusin::getList($where, 1, $page, 20, '*', 'data_time DESC, join_low');
        if(!$list) return Json::fail('暂无数据');
        return Json::success('ok', $list, RuleKpiBusin::getNum($where));
    }

    /**
     * 商务KPI规则编辑
     */
    public function setKpiBusinRule()
    {
        $param['id']        = Request()->param('id', 0);
        $param['admin_id']  = $this->user_id;
        $param['join_low']  = Request()->param('join_low', 0);
        $param['join_high'] = Request()->param('join_high', 0);
        $param['radio']     = Request()->param('radio', 0);
        $param['data_time'] = strtotime(Request()->param('data_time', 0));

        $flag = RuleKpiBusin::edit($param);
        if(!$flag) return Json::fail();
        return Json::success();
    }




    /** 获取KPI记录 */
    public function getKpiList()
    {   
        $page    = Request()->param('page', 1);
        $isStaff = Request()->param('is_staff', 0);

        $where = [];

        if($isStaff == 1){
            $where[] = ['user_id', '=', $this->user_id];
        }else if($isStaff == 0 && $this->user_id != 1){
            $sectionId = User::getVal(['id' => $this->user_id], 'section_id');
            $userIds = User::getCol(['section_id' => $sectionId], 'id');

            $where[] = ['user_id', 'in', $userIds];
        }

        $list = KpiRecord::getList($where, 1, $page, 20, '*', 'data_time DESC, id DESC');
        if($list === false) return Json::fail('暂无数据');

        $grade = [0 => '暂无', 1 => 'A', 2 => 'B', 3 => 'C', 4 => 'D', 5 => 'E'];

        foreach($list as &$info){
            $ruleKpiInfo = RuleKpi::getFind(['id' => $info['rule_kpi_id']]);

            $info['rule_radio']  = $ruleKpiInfo['radio'];
            $info['user_name']   = User::getVal(['id' => $info['user_id']], 'name');
            $info['data_time']   = date('Y-m', $info['data_time']);
            $info['grade']       = $grade[$info['grade']];
 
            unset($info['user_id']);
            unset($info['rule_kpi_id']);
        }

        return Json::success('ok', $list, KpiRecord::getNum($where));
    }

    /**
     * 新增KPI记录
     */
    public function addKpiRecord()
    {
        $param['rule_kpi_id']  = Request()->param('rule_kpi_id', 0);
        $param['total_target'] = Request()->param('total_target', 0);
        if($param['rule_kpi_id'] == 0) return Json::fail('KPI规则不能为空');

        $ruleKpiInfo = RuleKpi::getFind(['id' => $param['rule_kpi_id']]);
        if(!$ruleKpiInfo) return Json::fail('规则不存在');

        if($param['total_target'] < $ruleKpiInfo['total_low'] || $param['total_target'] > $ruleKpiInfo['total_high']){
            return Json::fail('目标业绩错误(应在' . $ruleKpiInfo['total_low'] . '~' . $ruleKpiInfo['total_high'] . '之间)');
        }

        $isAdd = KpiRecord::where(['user_id' => $this->user_id])->whereMonth('create_time')->find();
        if($isAdd) return Json::fail('本月已设置KPI规则,请勿重新提交');

        $param['user_id']  = $this->user_id;
        $param['data_time'] = strtotime($ruleKpiInfo['data_time']);

        $flag = KpiRecord::add($param);
        if(!$flag) return Json::fail('添加失败');
        return Json::success('添加成功');
    }

    /**
     * 更新日常表现分
     */
    public function setDaily()
    {
        $kpiRecordId = Request()->param('kpi_record_id', 0);
        $param       = Request()->param('param', '');
        if($kpiRecordId == 0) return Json::fail('KPI记录ID不能为空');
        if(empty($param)) return Json::fail('打分数据不能为空');
        $param = json_decode($param, true);

        foreach($param as $data){
            $dailyRuleInfo = KpiDailyRule::getFind(['id' => $data['id']]);
            if(!$dailyRuleInfo) return Json::fail('该考核项不存在');
            if(!$data['score']) return Json::fail($dailyRuleInfo['title'] . '分数不能为空');
            if($data['score'] > $dailyRuleInfo['score']) return Json::fail($dailyRuleInfo['title'] . '最高分值' . $dailyRuleInfo['score']);

            $addParam[] = [
                'user_id'       => $this->user_id,
                'kpi_record_id' => $kpiRecordId,
                'daily_rule_id' => $data['id'],
                'score'         => $data['score'],
                'remarks'       => $data['remarks'],
            ];
        }

        $kpiInfo = KpiRecord::getFind(['id' => $kpiRecordId]);

        $dailyInfo = KpiDaily::getFind(['kpi_record_id' => $kpiRecordId]);

        /** 新增打分记录 */
        if($dailyInfo) KpiDaily::del(['kpi_record_id' => $kpiRecordId]);
        $flag = KpiDaily::addAll($addParam);
        if(!$flag) return Json::fail();

        /** 总分 */
        $scoreArr = array_column($addParam, 'score');
        $score = array_sum($scoreArr);

        /** 更新KPI统计 */
        $kpiFlag = KpiRecord::edit([
            'id'    => $kpiRecordId, 
            'daily' => $score, 
            'score' => $kpiInfo['score'] + $score,
            'grade' => OkrRecord::getGrade($kpiInfo['score'] + $score),
        ]);

        if(!$kpiFlag) return Json::fail();
        return Json::success();
    }

    /**
     * 打分规则列表
     */
    public function getDailyRuleList()
    {
        $page        = Request()->param('page', 1);
        $type        = Request()->param('type', 1);
        $kpiRecordId = Request()->param('kpi_record_id', 0);

        switch ($type) {
            case 1:
                $list = KpiDailyRule::getList([], 1, $page, 20, '*', 'is_use DESC, id DESC');
                break;
            case 2:
                $list = KpiDailyRule::getList([], 0, 0, 0);
                break;
            case 3:
                if($kpiRecordId == 0) return Json::fail('KPI记录ID不能为空');
                $list = KpiDailyRule::getList(['is_use' => 1], 0, 0, 0);
                if(!$list) return Json::fail('请先设置打分规则');

                foreach($list as &$info){
                    $dailyInfo = KpiDaily::getFind(['daily_rule_id' => $info['id'], 'kpi_record_id' => $kpiRecordId]);

                    if($dailyInfo){
                        $info['score_now'] = $dailyInfo['score'];
                        $info['remarks']   = $dailyInfo['remarks'];
                    }else{
                        $info['score_now'] = '';
                        $info['remarks']   = '';
                    }
                }
                break;
            default:
                return Json::fail();
                break;
        }

        if(!$list) return Json::fail('暂无数据');
        return Json::success('ok', $list);
    }

    /**
     * 打分规则新增&编辑
     */
    public function setDailyRule()
    {
        $id    = Request()->param('id', 0);
        $param['title'] = Request()->param('title', '');
        $param['desc']  = Request()->param('desc', '');
        if(empty($param['desc'])) return Json::fail('考核项不能为空');

        if($id){
            $param['id'] = $id;
            $flag = KpiDailyRule::edit($param);
        }else{
            $flag = KpiDailyRule::add($param);
        }

        if(!$flag) return Json::fail();
        return Json::success();
    }

    /**
     * 打分规则开启&关闭
     */
    public function setDailyRuleIsUse()
    {
        $id = Request()->param('id', 0);
        if($id == 0) return Json::fail();
        if(KpiDailyRule::getNum(['is_use' => 1]) >= 3) return Json::fail('使用中考核项最多三个');

        $info = KpiDailyRule::getFind(['id' => $id]);
        if(!$info) return Json::fail();

        $flag = KpiDailyRule::edit(['id' => $id, 'is_use' => $info['is_use'] ? 0 : 1]);

        if(!$flag) return Json::fail();
        return Json::success();
    }

    /**
     * 同步KPI入职数据（定时任务|手动调用）
     */
    public function setKpiData()
    {
        KpiRecord::setKpiData(Request()->param('date', ''));
        return Json::success();
    }
}